import os
import json

from PyQt5.QtWidgets import *
from PyQt5.QtCore import *

import config
import encrypt

UserDir = config.RootDir + "/user"
IdFn = config.RootDir + "/ids"
RoleFn = config.RootDir + "/roles"

RoleNormal, RoleAdmin = range(2)


def _roles():
    if not os.path.isfile(RoleFn):
        return {}
    with open(RoleFn) as f:
        return json.loads(encrypt.decrypt(config.UserKey, f.read().encode()).decode())


def _save_roles(roles):
    with open(RoleFn, "w") as f:
        f.write(encrypt.encrypt(config.UserKey, json.dumps(roles).encode()).decode())


class User:
    def __init__(self, username):
        self.username = username
        key_fn = os.path.join(UserDir, username)
        self.password = ""

        if not os.path.isfile(key_fn):
            if not os.path.isdir(UserDir):
                os.makedirs(UserDir)
            self.key = encrypt.generate_key()
            self.set_password("123456")    # 初始密码
        else:
            with open(key_fn) as f:
                ss = f.read().splitlines()
                if len(ss) != 2:
                    self.key = ""
                    self.password = ""
                else:
                    self.key = encrypt.decrypt(config.UserKey, ss[0].strip().encode())
                    self.password = encrypt.decrypt(config.UserKey, ss[1].strip().encode()).decode()

    def set_password(self, password):
        if password == self.password or password == "" or self.username == "":
            return
        key_fn = os.path.join(UserDir, self.username)
        self.password = password
        with open(key_fn, "w") as f:
            f.write(encrypt.encrypt(config.UserKey, self.key).decode())
            f.write("\n")
            f.write(encrypt.encrypt(config.UserKey, self.password.encode()).decode())

    def check_password(self, password):
        return self.password == password

    def role(self):
        return _roles().get(self.username, RoleNormal)

    def is_admin(self):
        return self.username == "admin" or self.role() == RoleAdmin

    def set_role(self, role):
        roles = _roles()
        roles[self.username] = role
        _save_roles(roles)

    def rm_user(self, username):
        if username == "admin":
            return
        if self.role() != RoleAdmin:
            return
        key_fn = os.path.join(UserDir, username)
        if os.path.isfile(key_fn):
            os.remove(key_fn)
        roles = _roles()
        if username in _roles():
            del roles[username]
            _save_roles(roles)

    @staticmethod
    def user_names():
        return os.listdir(UserDir)

    @staticmethod
    def has_user(username):
        return username in User.user_names()

    @staticmethod
    def check_user(username, password):
        if not User.has_user(username):
            return None
        user = User(username)
        if user.check_password(password):
            return user
        return None


class UserManager(QDialog):
    def __init__(self, user):
        super().__init__()
        self.user = user
        self.setWindowTitle("用户管理")
        self.usernameEdit = QLineEdit()
        self.btnAdd = QPushButton("添加")
        self.btnDelete = QPushButton("删除")
        self.btnExplorer = QPushButton("文件管理")
        self.userWidget = QListWidget()
        self.roleEdit = QComboBox()
        self.roleEdit.addItems(("普通用户", "管理员"))
        hl = QHBoxLayout()
        hl.addWidget(QLabel("用户名："))
        hl.addWidget(self.usernameEdit)
        hl.addWidget(self.btnAdd)
        hl.addWidget(self.btnDelete)
        hl.addWidget(self.btnExplorer)
        hl.addWidget(self.roleEdit)
        vl = QVBoxLayout()
        vl.addLayout(hl)
        vl.addWidget(self.userWidget)
        self.setLayout(vl)

        for username in User.user_names():
            if username != "admin":
                self.userWidget.addItem(username)

        self.btnAdd.clicked.connect(self.add)
        self.btnDelete.clicked.connect(self.delete)
        self.btnExplorer.clicked.connect(self.explorer)
        self.userWidget.currentTextChanged.connect(self.current_user_change)
        self.roleEdit.currentIndexChanged[int].connect(self.change_role)
        self.resize(self.width(), 500)

    def change_role(self, role):
        item = self.userWidget.currentItem()
        if item is not None:
            User(item.text()).set_role(role)

    def current_user_change(self, username):
        user = User(username)
        self.roleEdit.setCurrentIndex(user.role())

    def add(self):
        username = self.usernameEdit.text()
        if username and username not in User.user_names():
            User(username)
            self.userWidget.addItem(username)

    def delete(self):
        item = self.userWidget.currentItem()
        if item is not None:
            self.user.rm_user(item.text())
            self.userWidget.takeItem(self.userWidget.currentRow())

    def explorer(self):
        from main_win import MainWin
        item = self.userWidget.currentItem()
        if item is not None:
            win = MainWin(User(item.text()))
            win.exec_()


# 初始化管理员帐号
if __name__ == "__main__":
    adminUser = User("admin")
    adminUser.set_role(RoleAdmin)
    print("管理员:", adminUser.username)
    print("密码：", adminUser.password)
